package org.lonetree.tc.core.dao;

import java.util.Set;
import org.lonetree.tc.core.Book;
import org.lonetree.tc.core.BookComment;
import org.lonetree.tc.core.Book.Isbn;
import org.lonetree.tc.core.exception.AttributeCannotBeNullException;
import org.lonetree.tc.core.exception.ItemAlreadyExistsException;
import org.lonetree.tc.core.exception.NoSuchItemException;
import org.lonetree.tc.core.exception.SearchException;
import org.lonetree.tc.core.search.BookCriteria;


/**
 * Get a Data Access Object for Books.
 */
public interface BookDAO{

	/**
	 * Get a Book.
	 *
	 * @param isbn - the ISBN of the book
	 * @return book
	 * @throws NoSuchItemException - if the book does not exist in the data store
	 */
	public Book getBook(Isbn isbn) throws NoSuchItemException;
	
	/**
	 * Create a Book.
	 *
	 * @param isbn - the ISBN of the book
	 * @return new book
	 * @throws ItemAlreadyExistsException - if the book already exists in the data store
	 */
	public Book createBook(Isbn isbn) throws ItemAlreadyExistsException;
	
	/**
	 * Remove a book.
	 *
	 * @param isbn - the ISBN of the book
	 * @throws NoSuchItemException - if the book does not exist in the data store
	 */
	public void removeBook(Isbn isbn) throws NoSuchItemException;
	
	/**
	 * Update a book in the data store.
	 *
	 * @param book - the book object with new data
	 * @throws NoSuchItemException - if the book does not exist in the data store
	 * @throws AttributeCannotBeNullException - if an attribute in cannot be null but that attribute is null in the book object
	 */
	public void updateBook(Book book) throws NoSuchItemException, AttributeCannotBeNullException;
	
	/**
	 * Find books.
	 *
	 * @param criteria - the criteria with which to search
	 * @return books matching the criteria
	 * @throws SearchException if an exception occurs during the search
	 */
	public Set<Book> findBooks(BookCriteria criteria) throws SearchException;
	
	/**
	 * Get all book comments that have been flagged.
	 *
	 * @return flagged comments
	 */
	public Set<BookComment> getFlaggedBookComments();
	
}
